#!/bin/bash
action=$1
type=$2
name=${3^}
if [ ! "$action" -o ! "$type" -o ! "$name" ]
then
    echo "Usage:"
    echo -e "\t./construct [action] [type] [name]"
    echo -e "\t     action -- make or rm"
    echo -e "\t     type -- clientTask or cliTask"
    echo -e "\t     name -- name of class will be build in code"
    exit 1
fi

case "$action" in
    "make");;
    "rm");;
    *)
        echo "Unknow action \"$1\", try \"make\" or \"rm\""
        exit 1
    ;;
esac

case "$type" in
    "clientTask") ;;
    "command") ;;
    "controller") ;;
    *)
        echo "Unknow type \"$1\", try \"clientTask\" or \"command\""
        exit 1
    ;;
esac

task_reg_file="src/core/boot/registerTask.cpp"
task_flag_file="src/task/TaskFlag.h"
task_h="#ifndef _TASK_${name^^}_H_
#define _TASK_${name^^}_H_
#include \"../TaskExecutor.h\"
DECLARE_TASK(${name})
#endif
"
task_cpp="#include \"${name}.h\"
#include <sys/socket.h>
#include \"SocketIO.h\"
namespace task {
    int $name::clientAction(socketinf serverinf, const char * arg, size_t len) {
        // Auto generate
        SocketIO sio(serverinf);

        // IMPORTANT trigger master execute serverAction 
        sio.socketWriter->sendFrame(TaskFlag::${name,,}, 0);
        

        return AUTO_CLOSE;
    }
    int $name::serverAction(socketinf clientinf, unsigned long long dataLength) {
        // Auto generate
        SocketIO sio(clientinf);

        return AUTO_CLOSE;
    }
}"

cli_reg_file="src/core/boot/registerCli.cpp"
cli_task_h="#ifndef _CLI_${name^^}_H_
#define _CLI_${name^^}_H_
#include \"../CliTask.h\"
DECLARE_CLI_EXECUTOR(${name})
#endif
"
cli_task_cpp="#include \"${name,,}/${name}.h\"
namespace Cli::${name,,} {
    void fun(std::vector<std::string> args) {
        // Command execute body
    }
}
MAKE_CLI_EXECUTOR(${name}, \"${name,,}\", \"command describe\", {
    Cli::${name,,}::fun(args);
})"

controller_h="#ifndef _CTRL_${name^^}_H_
#define _CTRL_${name^^}_H_
#include \"http.h\"
DECLARE_WEB_CONTROLLER(${name});
#endif"

controller_cpp="#include \"WebController/${name}.h\"
namespace controller {
    void ${name}::service(HttpRequest &request, HttpResponse &response) {
        std::string content;
        response.setContentLength(content.length())
                .setContentType(\"text/html;charset=utf-8\")
                .write(content);
    }
}
"

case "$action" in 
    "make")
        case "$type" in
            "clientTask")
                if [ -e src/task/${name} ]
                then
                    echo "clientTask ${name} has been existed"
                    exit 1
                fi
                mkdir "src/task/${name}"
                # 声明任务执行类
                echo -e "$task_h" > src/task/${name}/${name}.h

                # 定义任务执行类
                echo -e "$task_cpp" > src/task/${name}/${name}.cpp

                # 添加任务注册（添加头文件）
                file="../../task/${name}/${name}.h"
                line=`grep '#include' $task_reg_file | wc -l`
                sed -i "${line}a#include \"$file\"" $task_reg_file

                # 添加任务注册（添加注册语句）
                line=$((`grep } src/core/boot/registerTask.cpp -n | awk -F ":" '{print $1}'`-1))
                sed -i "${line}a\    nodeHandler.registerTask(TaskFlag::${name,,}, new task::${name}());" $task_reg_file

                # 添加任务标识码
                line=`grep \, src/task/TaskFlag.h -n | awk -F ":" '{print $1}' | sort | tail -n 1`
                sed -i "${line}a\    ${name,,}," src/task/TaskFlag.h
            ;;
            "command")
                if [ -e src/cli/${name,,} ]
                then
                    echo "Command task ${name} has been existed"
                    exit 1
                fi
                mkdir src/cli/${name,,}
                echo -e "$cli_task_h" > src/cli/${name,,}/$name.h
                echo -e "$cli_task_cpp" > src/cli/${name,,}/$name.cpp
                line1=`grep "#include" "$cli_reg_file" -n | tail -n 1 | awk -F ":" '{print $1}'`
                line2=`grep ");" "$cli_reg_file" -n | tail -n 1 | awk -F ":" '{print $1}'`
                sed -e "${line1}a#include \"cli/${name,,}/${name}.h\"" -e "${line2}a\    cliService.registerCmd(new cliTask::${name}());" $cli_reg_file -i
                
            ;;
            "controller")
                if [ -e src/http/WebController/${name} ]
                then
                    echo "Controller $name has been existed"
                    exit 1
                fi
                mkdir src/http/WebController/${name}
                echo -e "${controller_h}" > src/http/WebController/$name/$name.h
                echo -e "${controller_cpp}" > src/http/WebController/$name/$name.cpp
            ;;
        esac
    ;;
    "rm")
        case "$type" in
            "clientTask")
                if [ ! -e src/task/${name} ]
                then
                    echo "clientTask ${name} has not existed"
                    exit 1
                fi
                # 移除源代码
                rm -r src/task/${name}
                # 移除注册
                line1=`grep -n "#include \"../../task/$name" "$task_reg_file" | awk -F ":" '{print $1}'`
                line2=`grep -n "TaskFlag::${name,,}" "$task_reg_file" | awk -F ":" '{print $1}'`
                sed -e "${line1}d" -e "${line2}d" $task_reg_file -i

                # 移除标识码
                line1=`grep -n "${name,,}" "$task_flag_file" | awk -F ":" '{print $1}'`
                sed "${line1}d" $task_flag_file -i
            ;;
            "command")
                if [ ! -e src/cli/${name,,} ]
                then
                    echo "Command task ${name} has not existed"
                    exit 1
                fi
                rm -r "src/cli/${name,,}"
                line1=`grep -n "#include \"cli/${name,,}/$name" "$cli_reg_file" | awk -F ":" '{print $1}'`
                line2=`grep -n "new cliTask::$name()" "$cli_reg_file" | awk -F ":" '{print $1}'`
                sed -e "${line1}d" -e "${line2}d" "$cli_reg_file" -i
            ;;
        esac
    ;;
esac